<?php

namespace app\core;
use app\core\Config;
use app\core\ErrorHandler;
use Exception;


/**
 * 应用程序核心类
 * 
 * 该类负责应用程序的初始化和消息解析功能。
 */
class App
{
    use \app\core\Instance;

    /**
     * @var string 框架版本
     */
    private static $frameVersion = '2.0.0';

    /**
     * @var string 插件版本
     */
    public static $pluginVersion = '2.18.0';

    /**
     * @var string 框架名称
     */
    public static $frameName;

    /**
     * @var string 框架配置
     */
    public static $frameConfig;


    /**
     * @var string 框架名称的命名空间
     */
    public static $namespaceFrame;

    /**
     * @var object|null 消息解析类的实例
     */
    public static $messageClass;

    /**
     * 响应类实例
     * @var 
     */
    public static $responseClass;

    /**
     * @var object|null 消息处理类的实例
     */
    public static $messageHandlerClass;

    /**
     * @var string 程序运行目录
     */
    public static $rootPath;

    /**
     * 构造函数
     * 
     * 设置基础常量
     */
    public function __construct()
    {
        //关闭错误报告
        error_reporting(0);
        // 程序运行目录
        self::$rootPath = realpath(__DIR__ . '/../..');
        // 注册自定义错误处理函数
        //(new ErrorHandler)->vgg();
        set_error_handler('app\core\ErrorHandler::handleError');
        register_shutdown_function(['app\core\ErrorHandler', 'handleShutdown']);
        //        echo "123";

    }


    /**
     * 初始化应用程序
     */
    public function Initialization($frameName = false)
    {
        // 获取框架名称
        if ($frameName !== false) {
            self::$frameName = $frameName;
        } else {
            self::$frameName = Config::get('app', 'frame_name');
        }
        // 设置框架插件命名空间
        self::$namespaceFrame = "Frame\\" . self::$frameName . "\\";

        $funPah = self::$rootPath . '/app/function.php';
        if (file_exists($funPah)) {
            require_once $funPah;
        }
        return $this;
    }

    /**
     * 获取消息解析类
     * @throws \Exception
     * @return object|null
     */
    public function message()
    {
        $pluginMessageName = self::$namespaceFrame . 'Message';
        if (is_null(self::$messageClass)) {
            if (!class_exists($pluginMessageName)) {
                throw new Exception("框架" . self::$frameName . "运行时出错");
            }
            self::$messageClass = new $pluginMessageName;
        }
        return self::$messageClass;
    }


    /**
     * 消息处理
     * @return mixed
     */
    public function run()
    {
        $configPath = $this->getFramePath() . "/Config.php";
        if (file_exists($configPath)) {
            self::$frameConfig = require $configPath;
        }
        if (is_null(self::$messageHandlerClass)) {
            if (isset(self::$frameConfig['message_handler']) && self::$frameConfig['message_handler'] != "auto") {
                self::$messageHandlerClass = new self::$frameConfig['message_handler'];
            } else {
                self::$messageHandlerClass = new \app\MessageHandler;
            }
        }
        return (self::$messageHandlerClass)->run();
    }


    /**
     * 获取消息处理类
     * @return object|\app\MessageHandler|null
     */
    public function getMessageHandlerClass()
    {
        return self::$messageHandlerClass;
    }

    /**
     * 获取响应类实例
     * @throws \Exception
     * @return mixed
     */
    public function getResponseClass()
    {
        $pluginResponseName = self::$namespaceFrame . 'Response';
        if (is_null(self::$responseClass)) {
            if (!class_exists($pluginResponseName)) {
                throw new Exception("框架" . self::$frameName . "运行时出错");
            }
            self::$responseClass = new $pluginResponseName;
        }
        return self::$responseClass;
    }

    /**
     * 获取框架名称
     * 
     * @return string 路径
     */
    public function getFrameName()
    {
        return self::$frameName;
    }

    /**
     * 获取框架配置
     * 
     */
    public function getFrameConfig()
    {
        return self::$frameConfig;
    }


    /**
     * 获取运行目录
     * 
     * @return string 路径
     */
    public function getRootPath()
    {
        return self::$rootPath;
    }

    /**
     * 获取框架目录
     * 
     * @return string 路径
     */
    public function getFramePath()
    {
        return self::$rootPath . "/extend/Frame/" . self::$frameName;
    }

    /**
     * 获取缓存路径
     * 
     * @return string 路径
     */
    public function getRunTime()
    {
        return self::$rootPath . '/runtime';
    }

    /**
     * 获取框架版本
     * @return array 版本信息
     */
    public static function getVersion()
    {
        return [
            'frame' => self::$frameVersion,
            'plugin' => self::$pluginVersion
        ];
    }

}
